from typing import Literal, Optional

from fastapi import Depends, Request, Header

from .dependency import propfind_info, resource_model_router, resource_creator_router
from .handler import BaseHandler
from .resource_model import get_resource_creator, ResourceModel, ResourceCreator
from .webdav_router import WebDavRouter

router = WebDavRouter()


@router.options("/{any_path:path}")
async def method_options():
    return BaseHandler.options()


@router.propfind("/{any_path:path}")
async def method_propfind(
        res_obj: ResourceModel = Depends(resource_model_router),
        info=Depends(propfind_info)
):
    return await BaseHandler.propfind(res_obj, info)


@router.get("/{any_path:path}")
async def method_get(
        res_obj: ResourceModel = Depends(resource_model_router), rng=Header(default=None, alias="Range")
):
    return await BaseHandler.get(res_obj, rng, False)


@router.head("/{any_path:path}")
async def method_head(
        res_obj: ResourceModel = Depends(resource_model_router), rng=Header(default=None, alias="Range")
):
    return await BaseHandler.head(res_obj, rng)


@router.mkcol("/{any_path:path}")
async def method_mkcol(creator: ResourceCreator = Depends(resource_creator_router)):
    return await BaseHandler.mkcol(creator)


@router.put("/{any_path:path}")
async def method_put(request: Request, creator=Depends(get_resource_creator)):
    return await BaseHandler.put_file(creator, request)


@router.delete("/{any_path:path}")
async def method_delete(res_obj: ResourceModel = Depends(resource_model_router)):
    return await BaseHandler.delete(res_obj)


@router.move("/{any_path:path}")
async def method_move(
        res_obj: ResourceModel = Depends(resource_model_router),
        dst: Optional[str] = Header(alias='Destination', default=None),
        overwrite=Header(default='F')
):
    return await BaseHandler.move(res_obj, dst, overwrite)


@router.copy("/{any_path:path}")
async def method_copy(
        res_obj: ResourceModel = Depends(resource_model_router),
        dst: Optional[str] = Header(alias='Destination', default=None),
        overwrite: Literal["F", "T"] = Header(default='F'),
        depth: Literal["0", "infinity"] = Header(default="infinity")
):
    return await BaseHandler.copy(res_obj, dst, overwrite, depth)
